from crypt import crypt as c
from re import search as pesq
from os import environ, name as padraoSO, path

import funcoesPrincipais as fPrn

def mapeiaArquivoAtual(arquivoLeitura):
    arquivoLeitura.seek(0,0)

    usernames = []
    senhas = []
    UIDs = []
    GIDs = []
    descs = []
    homeDirs = []
    shells = []

    for linha in arquivoLeitura:
        usernames.append(linha.rsplit(":")[0])
        senhas.append(linha.rsplit(":")[1])
        UIDs.append(linha.rsplit(":")[2])
        GIDs.append(linha.rsplit(":")[3])
        descs.append(linha.rsplit(":")[4])
        homeDirs.append(linha.rsplit(":")[5])
        shells.append(linha.rsplit(":")[6])

    return usernames, senhas, UIDs, GIDs, descs, homeDirs, shells

def pegaNomeDoGrupo(GID):
    #if(padraoSO == 'posix'):
    if(path.exists("/etc/group")):
        arquivoLeitura = open("/etc/group", 'r')
        for linha in arquivoLeitura:
            if(GID == linha.rsplit(":")[2]):
                return linha.rsplit(":")[0]
    else:
        return "Não é possível verificar o conteúdo de /etc/group no sistema atual"

def geraUID(arquivoLeitura):
    retornoMapeiaArquivoAtual = mapeiaArquivoAtual(arquivoLeitura)[2]
    return max(list(map(int, retornoMapeiaArquivoAtual))) + 1 # retorna o número seguinte ao do maior ID encontrado

def verificaDuplicatas(username, UID, homeDir, arquivoLeitura):
    duplicados = []
    for nome in mapeiaArquivoAtual(arquivoLeitura)[0]:
        if(username == nome):
            duplicados.append("username")

    for userID in mapeiaArquivoAtual(arquivoLeitura)[2]:
        if(UID == userID):
            duplicados.append("UID")

    for diretorioHome in mapeiaArquivoAtual(arquivoLeitura)[5]:
        if(homeDir == diretorioHome):
            duplicados.append("homeDir")
            
    return duplicados

def listarGruposDoSistema():
    gruposArquivo = open("/etc/group", 'r')
    for linha in gruposArquivo:
        print("Grupo: {} | ID: {}".format(linha.rsplit(":")[0], linha.rsplit(":")[2]))

def loopPergunta(texto, opcional):
    while True:
        resposta = input(texto)
        if(texto.find("GID") != -1 and not resposta.isdigit()):
            listarGruposDoSistema()
        if(resposta or opcional):
            return resposta        

def salvarComo(caminhoArquivoOriginal):
    salvarComo = loopPergunta("Informe onde deseja salvar o arquivo ao fim deste ato: (opcional) ", True)
    if(not salvarComo):
        salvarComo = caminhoArquivoOriginal
    return salvarComo


def sanitizacaoDeInput(string): # função inacabada e em desenvolvimento
    problema = False

    return False


def exibeFormulario(arquivoLeitura):
    username = loopPergunta("Nome de usuário: ", False)
    senha = loopPergunta("Senha: ", False)

    UID = str(loopPergunta("UID (opcional): ", True))
    if(not UID):
        UID = geraUID(arquivoLeitura)
        
    
    GID = str(loopPergunta("GID (deixe em branco para ver as opções): ", False))
    
    desc = loopPergunta("Descrição (opcional): ", True)
    homeDir = loopPergunta("Diretório home (opcional - padrão: /home/username): ", True)
    if(not homeDir):
        homeDir = "/home/{}".format(username)

    if(verificaDuplicatas(username, UID, homeDir, arquivoLeitura)):
        print("ERRO: os seguintes dados digitados já se encontram em uso: {}".format(verificaDuplicatas(username, UID, homeDir, arquivoLeitura)))
        return "erro"

    shell = loopPergunta("Digite o caminho do shell desejado (opcional): ", True)
    if(not shell):
        shell = environ['SHELL'] # detecta o shell atual e define caso o usuário não especifique nada.

    if(sanitizacaoDeInput(username) or sanitizacaoDeInput(senha) or sanitizacaoDeInput(UID) or sanitizacaoDeInput(GID) or sanitizacaoDeInput(desc) or sanitizacaoDeInput(homeDir) or sanitizacaoDeInput(shell)):
        print("Caracteres indevidos foram usados")
        return "erro"
    
    return username, senha, UID, GID, desc, homeDir, shell

def geraShadow(username, senha):
    senhaEncriptada = c(senha)
    open("shadow", 'a').write("{}:{}\n".format(username, senhaEncriptada))

def atualizaShadow(username, novaSenha, operacao):
    with open("shadow", 'w') as arq:
        for linha in open("shadow", 'r').readlines():
            if(linha.rsplit(":")[0] != username):
                arq.write(linha)
            else:
                if(operacao == "editar"):
                    arq.write("{}:{}".format(username, c(novaSenha)))
